


#ifndef CATPEOPLE_H
#define CATPEOPLE_H



#include "category.h"
#include "person.h"



class CatPerson : public CatCollection
{
public:    
    virtual bool empty(Subject *owner = NULL);
    virtual bool one(Subject *owner = NULL);
    virtual uint8_t getCount(Subject *owner = NULL);
    virtual void generate( CollectionSubjects &subs, Subject *owner, uint8_t level );
    
protected:
    CatPerson();
    CatPerson( Subject *person );
};



class CatThisPerson : public CatPerson
{
public:    
    static Category *createCategory();
    virtual bool personal() const;
    virtual const CollectionSubjects &getSubjects( Subject *owner = NULL );
    virtual void generate( CollectionSubjects &subs, Subject *owner, uint8_t level );
    
protected:
    CatThisPerson();
};



class CatTheLeftPerson : public CatPerson
{
public:    
    static Category *createCategory( CollectionSubjects &subs );
    
protected:
    CatTheLeftPerson( Subject *person );
};



class CatTheRightPerson : public CatTheLeftPerson
{
public:    
    static Category *createCategory( CollectionSubjects &subs );
    
protected:
    CatTheRightPerson( Subject *person );
};



class CatMiddlePerson : public CatTheLeftPerson
{
public:    
    static Category *createCategory( CollectionSubjects &subs );
    
protected:
    CatMiddlePerson( Subject *person );
};



class CatColorPeople : public CatColor
{
public:
    static Category *createCategory( CollectionSubjects &people, Color::eColor col, Color::eColor max_col );
    virtual void generate( CollectionSubjects &subs, Subject *owner, uint8_t level );
    
protected:
    CatColorPeople( CollectionSubjects &people, Color::eColor col );
};



class CatNeighbours : public CatCollection
{
public:
    static Category *createCategory( CollectionSubjects &people );
    virtual bool one( Subject *owner = NULL );
    virtual const std::string &putText( Subject *owner = NULL );
    virtual const CollectionSubjects &getSubjects( Subject *owner = NULL );
    virtual void generate( CollectionSubjects &subs, Subject *owner, uint8_t level );
    
protected:
    CatNeighbours( CollectionSubjects &subs );
    void refill(Subject *owner);
    
    CollectionSubjects *m_pBaseSubjects;
    Subject *m_pLastOwner;
};



class CatFatPeople : public CatCollection
{
public:
    static Category *createCategory( CollectionSubjects &people );
    virtual void generate( CollectionSubjects &subs, Subject *owner, uint8_t level );

protected:
    CatFatPeople(){};
    CatFatPeople( CollectionSubjects &people );
};



class CatSlimPeople : public CatFatPeople
{
public:
    static Category *createCategory( CollectionSubjects &people );

protected:
    CatSlimPeople( CollectionSubjects &people );
};



class CatIncognitoPeople : public CatFatPeople
{
public:
    static Category *createCategory( CollectionSubjects &people );

protected:
    CatIncognitoPeople( CollectionSubjects &people );
};



class CatAllPeople : public CatAll
{
public:
    static Category *createCategory( CollectionSubjects &people );    
    virtual void generate( CollectionSubjects &subs, Subject *owner, uint8_t level );
    
protected:
    CatAllPeople( CollectionSubjects &people );
};



class CatName : public CatMutable
{
public:
    static Category *createCategory( CollectionSubjects &people, Subject *person );
    virtual bool empty(Subject *owner = NULL);
    virtual bool one(Subject *owner = NULL);
    virtual uint8_t getCount(Subject *owner = NULL);
    virtual void generate( CollectionSubjects &subs, Subject *owner, uint8_t level );
    
protected:
    CatName( CollectionSubjects &people, Subject *person );
    virtual void refill();
};



class CatType : public CatMutable
{
public:
    static Category *createCategory( CollectionSubjects &people, PersonType::eType type );
    virtual void generate( CollectionSubjects &subs, Subject *owner, uint8_t level );
    
protected:
    CatType( CollectionSubjects &people, PersonType::eType type );
    virtual void refill();
    
    PersonType m_PersonType;
};



class CatHonestPeople : public CatTruth
{
public:
    static Category *createCategory( CollectionSubjects &people );    
    virtual void generate( CollectionSubjects &subs, Subject *owner, uint8_t level );
    
protected:
    CatHonestPeople( CollectionSubjects &people );
};



class CatLyingPeople : public CatLying
{
public:
    static Category *createCategory( CollectionSubjects &people );    
    virtual void generate( CollectionSubjects &subs, Subject *owner, uint8_t level );
    
protected:
    CatLyingPeople( CollectionSubjects &people );
};



#endif
